//
// Created by zjb on 2020/10/11.
//
#include<stdio.h>
#include<thread>
#include<chrono>
#include "MediaExporter/MediaExporter.h"
using namespace  liyuvideo;
char *audio_src1 = "c:\\test\\out.pcm";
FILE* fAudioSrc1 = NULL;
char *audio_src2 = "c:\\test\\m.pcm";
FILE* fAudioSrc2 = NULL;
class MyVideoSource:public liyuvideo::VideoSource{
public:
    virtual void feedVideoFrame(std::shared_ptr<MyMediaBuf>& pVideoFrame) override{
        static int frame_index = 0;
        std::this_thread::sleep_for(std::chrono::milliseconds(1));
        static uint32_t ts2 = 0;
        int width = 1280;
        int height = 720;
        int len = width*height*3;
        pVideoFrame = std::make_shared<MyMediaBuf>(new char[len],len);
        pVideoFrame->m_ts = ts2;
        if(frame_index==1500){
            pVideoFrame->m_bEnd = true;
        }
        ts2+=40;
        //fill yuv buffer

        int x, y, i;
        i = frame_index;
        char* yPtr = pVideoFrame->m_buf;
        char* uPtr = pVideoFrame->m_buf+width*height;
        char* vPtr = pVideoFrame->m_buf+width*height*5/4;
        int strideY = width;
        int strideU = height/2;
        int strideV = height/2;
        /* Y */
        for (y = 0; y < height; y++)
            for (x = 0; x < width; x++)
               yPtr[y * strideY + x] = x + y + i * 3;

        /* Cb and Cr */
        for (y = 0; y < height / 2; y++) {
            for (x = 0; x < width / 2; x++) {
                uPtr[y *strideU + x] = 128 + y + i * 2;
                vPtr[y *strideV+ x] = 64 + x + i * 5;
            }
        }
        frame_index++;
    }
};
class MyAudioSource:public liyuvideo::AudioSource{
public:
    virtual void feedAudioFrame(std::shared_ptr<MyMediaBuf>& pAudioFrame) override{
        static bool bEndFile = false;
        static float ts2 = 2000;
        int len = 1024*4;
        if(bEndFile){
            return;
        }
        pAudioFrame = std::make_shared<MyMediaBuf>(new char[len],len);
        pAudioFrame->m_ts = (uint32_t)ts2;
        ts2+=23.22;
        //从文件读出pcm
        int ret = fread(pAudioFrame->m_buf,4,1024,fAudioSrc1);
        int16_t *p = (int16_t*)pAudioFrame->m_buf;
        for(int i=0;i<len/2;i++){
            p[i]=0.6*p[i];
        }
        if(ret<=0||ts2>23000){
            printf("end of file,we will close it\n");
            pAudioFrame = nullptr;
            bEndFile = true;
            fclose(fAudioSrc1);
        }
    }
};
class MyAudioSource2:public liyuvideo::AudioSource{
public:
    virtual void feedAudioFrame(std::shared_ptr<MyMediaBuf>& pAudioFrame) override{
        static bool bEndFile = false;
        static float ts2 = 15000;
        int len = 1024*4;
        if(bEndFile){
            return;
        }
        pAudioFrame = std::make_shared<MyMediaBuf>(new char[len],len);
        pAudioFrame->m_ts = (uint32_t)ts2;
        ts2+=23.22;
        //从文件读出pcm
        int ret = fread(pAudioFrame->m_buf,4,1024,fAudioSrc2);
        if(ret<=0){
            printf("end of file 2,we will close it\n");
            pAudioFrame = nullptr;
            bEndFile = true;
            fclose(fAudioSrc2);
        }
    }
};
int main(){
    fAudioSrc1 = fopen(audio_src1, "rb");
    if (!fAudioSrc1) {
        fprintf(stderr, "Could not open %s\n",audio_src1);
        exit(1);
    }
    fAudioSrc2 = fopen(audio_src2, "rb");
    if (!fAudioSrc2) {
        fprintf(stderr, "Could not open %s\n",audio_src1);
        exit(1);
    }
    std::shared_ptr<liyuvideo::ExportConfig> config = std::make_shared<liyuvideo::ExportConfig>();
    config->videoWidth = 1280;
    config->videoHeight = 720;
    MediaExport* inst = liyuvideo::getMediaExport();
    MyVideoSource videoSource;
    config->m_pVideoSource = &videoSource;
    config->m_pCompleteEvent = [=](){
        printf("onComplete event\n");
    };
    for(int i=0;i<3;i++){
        //config->m_pAudioSourceList[i] = new MyAudioSource();
    }
    config->m_pAudioSourceList[0] = new MyAudioSource();
    config->m_pAudioSourceList[1] = new MyAudioSource2();
    config->m_videoFile = "C:\\Users\\zengjianbin\\test.mp4";
    printf("test media mixer,%d\n",inst->initModule(config));
    getchar();
    inst->releaseModule();
    return 0 ;
}
